今天來認識很酷的布林運算。
兩種 Boolean 運算子 and
, or
其實在 Python 中的運作大相徑庭!
or
X or Y
: 如果 X 為假,return Y,否則計算並返回 X
來實驗看看:
'' or 'abc'
'abc'
0 or 100
100
[] or [1, 2, 3]
[1, 2, 3]
[1, 2] or [1, 2, 3]
[1, 2]
實驗成功!而且你發現到了嗎? Python 甚至根本不管 Y
的真假值,直接回傳 Y
!
運算子左邊的運算元決定了返回的結果。
如果 X
為真因而返回 X
,Y
甚至都不會被計算到 - 這就是昨天學到的短路!!!
也許我們可以自己寫一個 or
運算子如下:
def _or(x, y):
if x:
return x
else:
return y
print(_or(0, 100) == (0 or 100))
print(_or(None, 'n/a') == (None or 'n/a'))
print(_or('abc', 'n/a') == ('abc' or 'n/a'))
True
True
True
但這個沒比 Python 為你準備的 or
好!
因為我們這裡寫的 _or
function 永遠都會運算 x 和 y (因為它們被當成引數傳入) - 就沒有享受到短路的好處了。
1 or 1/0
1
_or(1, 1/0)
---------------------------------------------------------------------------
ZeroDivisionError Traceback (most recent call last)
/Users/maotingyang/Downloads/Booleans - Boolean Operators.ipynb Cell 15 in <cell line: 1>()
----> <a href='vscode-notebook-cell:/Users/maotingyang/Downloads/Booleans%20-%20Boolean%20Operators.ipynb#X20sZmlsZQ%3D%3D?line=0'>1</a> _or(1, 1/0)
ZeroDivisionError: division by zero
X and Y
: 如果 X 為假,返回 X,否則運算並返回 Y。
又來了,右邊的 Y
只有在 X
為假時會被運算到(短路)。
s1 = None
s2 = ''
s3 = 'abc'
print(s1 and s1[0])
print(s2 and s2[0])
print(s3 and s3[0])
None
a
print((s1 and s1[0]) or '')
print((s2 and s2[0]) or '')
print((s3 and s3[0]) or '')
a
發現了嗎,這種短路特性可以讓我們遇到 s
是 None
或空字串時,回傳一個預設值,很是方便:
print((s1 and s1[0]) or 'n/a')
print((s2 and s2[0]) or 'n/a')
print((s3 and s3[0]) or 'n/a')
n/a
n/a
a
The not
function:not
則是會根據物件的真假值返回相反的布林值。
not 'abc'
False
not []
True
bool(None)
False
not None
True
好啦,今天就到這邊,明天見!
參考:Python 3: Deep Dive (Part 1 - Functional)